package main

import (
	"database/sql"
	"net/http"
	"strconv"

	"github.com/labstack/echo/v4"
	"gorm.io/gorm"
)

type Comment struct {
	gorm.Model
	Content string `json:"content"   validate:"required"`
	// Reply to commit_id
	ReplyTo   sql.NullInt32 `json:"reply_to"`
	PostId    uint          `json:"post_id"   validate:"required"`
	Name      string        `json:"name" validate:"required"`
	Contacter string        `json:"contacter"`
	RealIp    string        `json:"real_ip" validate:"ip"`
}

func CommentRegister(e *echo.Echo) {
	g := e.Group("/api/comments")
	g.POST("/", commentCreate)
	g.DELETE("/:id/", commentDelete, NeedAuth)
}

func commentCreate(c echo.Context) error {
	db := newDBSession(c)
	type CommentCreate struct {
		Content   string `json:"content" validate:"required"`
		ReplyTo   uint   `json:"reply_to"`
		PostId    uint   `json:"post_id" validate:"required"`
		Name      string `json:"name" validate:"required"`
		Contacter string `json:"contacter"`
	}
	var comment CommentCreate
	if err := c.Bind(&comment); err != nil {
		return echo.NewHTTPError(http.StatusBadRequest, err.Error())
	}
	if err := c.Validate(comment); err != nil {
		return echo.NewHTTPError(http.StatusBadRequest, err.Error())
	}

	var newcomment Comment
	newcomment.Content = comment.Content
	newcomment.PostId = comment.PostId
	if comment.ReplyTo != 0 {
		newcomment.ReplyTo.Valid = true
		newcomment.ReplyTo.Int32 = int32(comment.ReplyTo)
	}
	newcomment.Name = comment.Name
	newcomment.Contacter = comment.Contacter

	// 检查 reply_to 对应 commit_id
	if newcomment.ReplyTo.Valid {
		if result := db.First(&Comment{}, newcomment.ReplyTo.Int32); result.Error != nil {
			return echo.NewHTTPError(http.StatusBadRequest, "Reply to ID 不存在")
		}
	}

	if result := db.Create(&newcomment); result.Error != nil {
		return echo.NewHTTPError(http.StatusBadRequest, result.Error.Error())
	}
	return c.String(http.StatusCreated, "ok")
}

func commentDelete(c echo.Context) error {
	db := newDBSession(c)
	var commit Comment
	id, err := strconv.Atoi(c.Param("id"))
	if err != nil {
		return echo.NewHTTPError(http.StatusBadRequest, err.Error())
	}
	user, err := getUser(c)
	if err != nil || !user.IsAdmin {
		return echo.NewHTTPError(http.StatusUnauthorized, "需要管理员才能删除")
	}
	if result := db.Delete(&commit, id); result.Error != nil {
		return echo.NewHTTPError(http.StatusBadRequest, result.Error.Error())
	}
	return c.String(http.StatusOK, "ok")
}
